package api.utils;

import api.interfaceapi.APIMsgParams;
import okhttp3.*;
import okio.Buffer;
import okio.BufferedSource;

import java.io.EOFException;
import java.io.IOException;
import java.nio.charset.Charset;
import java.nio.charset.UnsupportedCharsetException;

public class MyHttpLoggingInterceptor implements Interceptor {
    private static final Charset UTF8 = Charset.forName("UTF-8");
    private APIMsgParams apiMsgParams;
    String apiAddress;
    String apiParams;
    String apiResponse;

    public MyHttpLoggingInterceptor(APIMsgParams apiMsgParams) {
        this.apiMsgParams = apiMsgParams;
    }

    public void setAPIMsgParams(APIMsgParams apiMsgParams) {
        this.apiMsgParams = apiMsgParams;
    }

    @Override
    public Response intercept(Chain chain) throws IOException {
        Request request = chain.request();
        Response response = chain.proceed(request);
        ResponseBody responseBody = response.body();
        RequestBody requestBody = request.body();

        apiAddress = request.url().url().toString();
        boolean hasRequestBody = requestBody != null;
        long contentLength = responseBody.contentLength();
        //编码设为UTF-8
        Charset charset = UTF8;
        MediaType contentTypeResponseBody = responseBody.contentType();
        Buffer bufferResponseBody = responseBody.source().buffer();
        BufferedSource source = responseBody.source();
        source.request(Long.MAX_VALUE); // Buffer the entire body.


        if (hasRequestBody) {
            if (requestBody.contentType() != null) {
                System.out.println("Content-Type: " + requestBody.contentType());
            }
            if (requestBody.contentLength() != -1) {
                System.out.println("Content-Length: " + requestBody.contentLength());
            }
        }
        if (requestBody != null) {
            if (contentLength != 0) {
                Buffer buffer = new Buffer();
                requestBody.writeTo(buffer);
                //编码设为UTF-8
                MediaType contentType = requestBody.contentType();
                if (contentType != null) {
                    charset = contentType.charset(UTF8);
                }
                if (isPlaintext(buffer)) {
                    apiParams = buffer.readString(charset);
                    System.out.println("参数" + apiParams);
                } else {
                    System.out.println("--> END " + request.method() + " (binary " + requestBody.contentLength() + "-byte body omitted)");
                }
            }
        }

        if (contentTypeResponseBody != null) {
            try {
                charset = contentTypeResponseBody.charset(UTF8);
            } catch (UnsupportedCharsetException e) {
                //Couldn't decode the response body; charset is likely malformed.
                return response;
            }
        }

        if (!isPlaintext(bufferResponseBody)) {
            System.out.println("<-- END HTTP (binary " + bufferResponseBody.size() + "-byte body omitted)");
            return response;
        }

        if (contentLength != 0) {
            apiResponse = bufferResponseBody.clone().readString(charset);
            System.out.println("响应数据》》" + apiResponse.replace("/n",""));
        }

        if (null != apiMsgParams) {
            apiMsgParams.getErrMsg(apiAddress, apiParams, apiResponse);
        }
        return response;
    }

    /**
     * Returns true if the body in question probably contains human readable text. Uses a small sample
     * of code points to detect unicode control characters commonly used in binary file signatures.
     */
    static boolean isPlaintext(Buffer buffer) throws EOFException {
        try {
            Buffer prefix = new Buffer();
            long byteCount = buffer.size() < 64 ? buffer.size() : 64;
            buffer.copyTo(prefix, 0, byteCount);
            for (int i = 0; i < 16; i++) {
                if (prefix.exhausted()) {
                    break;
                }
                int codePoint = prefix.readUtf8CodePoint();
                if (Character.isISOControl(codePoint) && !Character.isWhitespace(codePoint)) {
                    return false;
                }
            }
            return true;
        } catch (EOFException e) {
            return false; // Truncated UTF-8 sequence.
        }
    }

    private boolean bodyEncoded(Headers headers) {
        String contentEncoding = headers.get("Content-Encoding");
        return contentEncoding != null && !contentEncoding.equalsIgnoreCase("identity");
    }
}
